﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.Practices.EnterpriseLibrary.ExceptionHandling;
using Microsoft.Practices.EnterpriseLibrary.ExceptionHandling.Logging;

namespace Reconciliation.Data
{
    public partial class Order
    {
        public static Domain.Order MapDataToDomain(Data.Order dataOrder)
        {            
            Domain.OrderDetail domainOrdDet = null;
            Domain.Order domainOrder = new Reconciliation.Domain.Order();
            if(dataOrder.Bank != null)
                domainOrder.Bank = Bank.MapDataToDomain(dataOrder.Bank);
            if (dataOrder.Case != null)
                domainOrder.Case = Case.MapDataToDomain(dataOrder.Case);
            if (dataOrder.Cashpoint != null)
                domainOrder.Cashpoint = Cashpoint.MapDataToDomain(dataOrder.Cashpoint);
            if (dataOrder.Cpc != null)
                domainOrder.Cpc = Data.Cpc.MapDataToDomain(dataOrder.Cpc);
            domainOrder.CollectionDate = dataOrder.CollectionDate.Value ;
            domainOrder.DeliveryDate = dataOrder.DeliveryDate.Value ;
            if(dataOrder.Invoice != null)
                domainOrder.Invoice = Invoice.MapDataToDomain(dataOrder.Invoice) ;
            if (dataOrder.Location != null)
                domainOrder.Location = Location.MapDataToDomain(dataOrder.Location) ;
            domainOrder.OrderDate = dataOrder.OrderDate ;
            domainOrder.OrderID = dataOrder.OrderID ;
            domainOrder.OrderReferenceID = dataOrder.OrderReferenceID ;
            domainOrder.OrderType = dataOrder.OrderType ;
            if (dataOrder.User != null)
                domainOrder.User = User.MapDataToDomain(dataOrder.User);
            foreach (Data.OrderDetail ordDet in dataOrder.OrderDetail)
            {
                domainOrdDet = Data.OrderDetail.MapDataToDomain(ordDet);
                domainOrder.OrdreDetailList.Add(domainOrdDet);                
            }
            return domainOrder;
        }

        public static List<Domain.Order> GetOrderList(int invoiceID)
        {
            try
            {
                List<Domain.Order> domainOrderList = new List<Reconciliation.Domain.Order>();
                Domain.Order domainOrder = null;
                ReconciliationEntities recEnt = new ReconciliationEntities();
                List<Data.Order> dataOrderList = (from o in recEnt.Order.Include("OrderDetail").Include("Case").Include("Bank").Include("Location").
                                                      Include("Location.State").Include("Case.CaseAuditorComment").Include("Case.CaseClientComment").
                                                      Include("Case.CaseAttachment").Include("Case.CaseAuditorComment.User").Include("Cpc")
                                                  where o.Invoice.InvoiceID.Equals(invoiceID)
                                                  select o).ToList();

                foreach (Data.Order o in dataOrderList)
                {
                    domainOrder = Order.MapDataToDomain(o);
                    domainOrderList.Add(domainOrder);
                }
                return domainOrderList;
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Database exception occured please try again later.");
            }
        }

        public static List<Domain.Order> GetOrderList(DateTime startDate, DateTime endDate)
        {
            try
            {
                List<Domain.Order> domainOrderList = new List<Reconciliation.Domain.Order>();
                Domain.Order domainOrder = null;
                ReconciliationEntities recEnt = new ReconciliationEntities();
                int startDay = startDate.Day; int startYear = startDate.Year; int startMonth = startDate.Month;
                int endDay = endDate.Day; int endYear = endDate.Year; int endMonth = endDate.Month;
                startDate = new DateTime(startDate.Year, startDate.Month, startDate.Day, 0, 0, 0);
                endDate = new DateTime(endDate.Year, endDate.Month, endDate.Day, 23, 59, 59);
                List<Data.Order> dataOrderList = (from o in recEnt.Order.Include("Invoice").Include("OrderDetail").Include("Case").Include("Bank").
                                                      Include("Location").Include("Location.State").Include("Case.CaseAuditorComment").
                                                      Include("Case.CaseClientComment").Include("Case.CaseAttachment").Include("Cpc").
                                                      Include("Case.CaseAuditorComment.User")
                                                  where o.OrderDate >= startDate && o.OrderDate <= endDate
                                                  select o).ToList();
                foreach (Data.Order o in dataOrderList)
                {
                    domainOrder = Order.MapDataToDomain(o);
                    domainOrderList.Add(domainOrder);
                }
                return domainOrderList;
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Database exception occured please try again later.");
            }
        }

        public static Domain.Order GetOrder(int orderID)
        {
            try
            {
                Domain.Order domainOrder = new Reconciliation.Domain.Order();
                ReconciliationEntities recEnt = new ReconciliationEntities();
                Data.Order dataOrder = (from o in recEnt.Order.Include("OrderDetail").Include("OrderDetail.Denomination").Include("Case").Include("Bank").Include("Cpc").
                                                      Include("Case.CaseAuditorComment").Include("Case.CaseClientComment").
                                                      Include("Case.CaseAttachment").Include("Case.CaseAuditorComment.User")
                                        where o.OrderID.Equals(orderID)
                                        select o).FirstOrDefault();

                if (dataOrder != null)
                    domainOrder = Order.MapDataToDomain(dataOrder);
                return domainOrder;
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Database exception occured please try again later.");
            }
        }

        public static List<Domain.Order> GetGeneratedOrderList()
        {
            try
            {
                Domain.Order domainOrder = null;
                List<Domain.Order> domainOrderList = new List<Reconciliation.Domain.Order>();
                ReconciliationEntities recEnt = new ReconciliationEntities();
                List<Data.Order> dataOrderList = (from o in recEnt.Order
                                                  where o.Status.Equals("New")
                                                  select o).ToList();
                foreach (Data.Order dataOrder in dataOrderList)
                {
                    domainOrder = Data.Order.MapDataToDomain(dataOrder);
                    domainOrderList.Add(domainOrder);
                }
                return domainOrderList;
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Database exception occured please try again later.");
            }
        }

        public static void SetPackagingOrderDetail(Domain.Order domainOrder)
        {
            try
            {
                using (ReconciliationEntities recEnt = new ReconciliationEntities())
                {
                    Data.Order dataOrder = recEnt.Order.Where(o => o.OrderID.Equals(domainOrder.OrderID)).FirstOrDefault();
                    if (dataOrder != null)
                    {
                        dataOrder.Status = domainOrder.Status;
                        recEnt.SaveChanges();
                    }
                }
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Order does not exists.");
            }
        }

        public static void SetUnPackagingOrderDetail(Domain.Order domainOrder)
        {
            try
            {
                using (ReconciliationEntities recEnt = new ReconciliationEntities())
                {
                    Data.Order dataOrder = recEnt.Order.Where(o => o.OrderID.Equals(domainOrder.OrderID)).FirstOrDefault();
                    if (dataOrder != null)
                    {
                        dataOrder.Status = domainOrder.Status;
                        recEnt.SaveChanges();
                    }
                }
            }
            catch (Exception ex)
            {
                ExceptionPolicy.HandleException(ex, "Exception Policy");
                throw new Domain.ReconciliationException("Order does not exists.");
            }
        }
    }
}
